1 module hunt.cache.memory; 2 3 import hunt.cache.cache; 4 import hunt.cache.store; 5 import hunt.cache.nullable; 6 7 import core.stdc.stdlib; 8 import core.stdc.string; 9 import core.stdc.time; 10 11 import std.variant; 12 import std.conv; 13 14 public: 15 16 class MemoryCache 17 { 18 Nullable!V get(V)(string key) 19 { 20 synchronized(this) 21 { 22 return get_inter!V(key); 23 } 24 } 25 26 Nullable!V[string] getall(V)(string[] keys) 27 { 28 Nullable!V[string] mapv; 29 30 synchronized(this) 31 { 32 foreach(k; keys) 33 { 34 mapv[k] = get_inter!V(k); 35 } 36 } 37 38 return mapv; 39 } 40 41 bool containsKey(string key) 42 { 43 synchronized(this) 44 { 45 return (key in cacheData) ? true : false; 46 } 47 } 48 49 void put(V)(string key, V v, uint expired = 0) 50 { 51 synchronized(this) 52 { 53 put_inter(key, v, expired); 54 } 55 } 56 57 bool putifAbsent(V)(string key, V v) 58 { 59 synchronized(this) 60 { 61 bool ret = (key in cacheData) ? true : false; 62 63 if (!ret) 64 { 65 put_inter!V(key, v, 0); 66 67 return true; 68 } 69 70 return false; 71 } 72 } 73 74 void putAll(V)(V[string] maps, uint expired = 0) 75 { 76 synchronized(this) 77 { 78 foreach(k, v; maps) 79 { 80 put_inter(k, v, expired); 81 } 82 } 83 } 84 85 bool remove(string key) 86 { 87 synchronized(this) 88 { 89 if (key in cacheTime) 90 { 91 cacheTime.remove(key); 92 } 93 94 bool ret = (key in cacheData) ? true : false; 95 96 if (ret) 97 { 98 cacheData.remove(key); 99 } 100 101 return ret; 102 } 103 } 104 105 void removeAll(string[] keys) 106 { 107 synchronized(this) 108 { 109 foreach(k; keys) 110 { 111 if (k in cacheTime) 112 { 113 cacheTime.remove(k); 114 } 115 116 if (k in cacheData) 117 { 118 cacheData.remove(k); 119 } 120 } 121 } 122 } 123 124 void clear() 125 { 126 synchronized(this) 127 { 128 cacheData.clear(); 129 cacheTime.clear(); 130 } 131 } 132 133 this(string args = "") 134 { 135 } 136 137 ~this() 138 { 139 clear(); 140 } 141 142 protected: 143 144 Variant[string] cacheData; 145 uint[string] cacheTime; 146 147 Nullable!V get_inter(V)(string key) 148 { 149 Nullable!V v; 150 151 if (key !in cacheTime) //not set ttl 152 { 153 if (key in cacheData) 154 { 155 v.bind(cacheData[key].get!V); 156 } 157 158 return v; 159 } 160 else 161 { 162 uint tick = cacheTime[key]; 163 uint now = cast(uint)time(null); 164 165 if (tick < now) // remove 166 { 167 cacheTime.remove(key); 168 cacheData.remove(key); 169 170 return v; 171 } 172 else 173 { 174 v.bind(cacheData[key].get!V); 175 176 return v; 177 } 178 } 179 } 180 181 void put_inter(V)(string key, V v, uint expired) 182 { 183 if (expired == 0) 184 { 185 if (key in cacheTime) 186 { 187 cacheTime.remove(key); 188 } 189 } 190 else 191 { 192 cacheTime[key] = expired + cast(uint)time(null); 193 } 194 195 cacheData[key] = v; 196 } 197 }